package com.deep.deepenterpise.service.gas.impl;

import com.deep.deepenterpise.common.DrGson;
import com.deep.deepenterpise.common.gas.DrGasAuthKey;
import com.deep.deepenterpise.common.gas.DrGovernmentApiUrl;
import com.deep.deepenterpise.common.redis.GasKey;
import com.deep.deepenterpise.common.resources.DrApiResources;
import com.deep.deepenterpise.common.util.DrCommonUtil;
import com.deep.deepenterpise.common.util.DrOkHttpUtil;
import com.deep.deepenterpise.model.entity.DrCheckItem;
import com.deep.deepenterpise.model.to.gas.*;
import com.deep.deepenterpise.model.vo.gas.*;
import com.deep.deepenterpise.service.gas.IDrGovernmentApi;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * @author xyz
 * @version 1.0
 * @title GovernmentApi
 * @description TODO 对接政府端API
 * @create 2024/5/14 03:13
 */
@Service
@Slf4j
public class DrGovernmentApi implements IDrGovernmentApi {
    @Resource
    private DrApiResources drApiResources;
    @Resource
    private DrGasAuthKey drGasAuthHandler;


    /**
     * @return java.lang.String
     * @Auth xyz
     * @Desc //TODO 获取token
     * @Time 11:33 2024/5/15
     * @Param [unitKey, unitSecret]
     */
    private String postDrGasToken(String unitKey, String unitSecret) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_GAS_TOKEN;
        Map<String, String> body = new HashMap<>();
        body.put("drKey", unitKey);
        body.put("drSecret", unitSecret);
        return DrOkHttpUtil.httpPost(url, null, body);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO 添加单位
     * @Time 11:41 2024/5/15
     * @Param [drAddUnitTo, drUnitKey]
     */
    @Override
    public DrGasResultVo postDrAddUnit(DrAddUnitTo drAddUnitTo, String drUnitKey) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_UNIT;
        return postApi(drAddUnitTo, url, drUnitKey);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO 企业液化气运输车辆档案 /录入/更新/删除
     * @Time 09:49 2024/5/14
     * @Param [drAddUnitTos, drUnitKey]
     */
    @Override
    public DrGasResultVo postDrAddCart(List<DrAddCartTo> drAddUnitTos, String drUnitKey) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_CART;
        return postApi(drAddUnitTos, url, drUnitKey);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO 企业液化气瓶配送记录上传
     * @Time 10:30 2024/5/14
     * @Param [drAddDeliveryNoticeTos]
     */
    @Override
    public DrGasResultVo postDrAddDeliveryNotice(List<DrAddDeliveryNoticeTo> drAddDeliveryNoticeTos) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_DELIVERY_NOTICE;
        return postApi(drAddDeliveryNoticeTos, url, null);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO 企业人员信息 /录入/更新/删除
     * @Time 16:31 2024/5/15
     * @Param [drAddPersonnelTos, drUnitKey]
     */
    @Override
    public DrGasResultVo postDrAddPersonnel(List<DrAddPersonnelTo> drAddPersonnelTos, String drUnitKey) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_PERSONNEL;
        return postApi(drAddPersonnelTos, url, drUnitKey);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO 企业客户信息录入/更新/删除
     * @Time 10:40 2024/5/14
     * @Param [drAddClienteleTos]
     */
    @Override
    public DrGasResultVo postDrAddClientele(List<DrAddClienteleTo> drAddClienteleTos) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_CLIENTELE;
        return postApi(drAddClienteleTos, url, null);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO 企业液化气瓶信息录入/更新/删除
     * @Time 10:43 2024/5/14
     * @Param [drAddGasCylinderTos]
     */
    @Override
    public DrGasResultVo postDrAddGasCylinder(List<DrAddGasCylinderTo> drAddGasCylinderTos, String drUnitKey) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_GAS_CYLINDER;
        return postApi(drAddGasCylinderTos, url, drUnitKey);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO 企业液化气气瓶入户检查上传
     * @Time 10:46 2024/5/14
     * @Param [drAddLoginCheckTos]
     */
    @Override
    public DrGasResultVo postDrAddLoginCheck(List<DrAddLoginCheckTo> drAddLoginCheckTos) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_LOGIN_CHECK;
        return postApi(drAddLoginCheckTos, url, null);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO 企业液化气气瓶充装记录上传
     * @Time 10:49 2024/5/14
     * @Param [drAddRefillNoticeTos, drUnitKey]
     */
    @Override
    public DrGasResultVo postDrAddRefillNotice(List<DrAddRefillNoticeTo> drAddRefillNoticeTos, String drUnitKey) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_REFILL_NOTICE;
        return postApi(drAddRefillNoticeTos, url, drUnitKey);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO 企业液化气气瓶充装前检查记录上传
     * @Time 10:50 2024/5/14
     * @Param [drAddRefillBeforeTos, drUnitKey]
     */
    @Override
    public DrGasResultVo postDrAddRefillBefore(List<DrAddRefillBeforeTo> drAddRefillBeforeTos, String drUnitKey) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_REFILL_BEFORE;
        return postApi(drAddRefillBeforeTos, url, drUnitKey);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO 企业液化气气瓶充装后检查记录上传
     * @Time 10:50 2024/5/14
     * @Param [drAddRefillAfterTos, drUnitKey]
     */
    @Override
    public DrGasResultVo postDrAddRefillAfter(List<DrAddRefillAfterTo> drAddRefillAfterTos, String drUnitKey) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_REFILL_AFTER;
        return postApi(drAddRefillAfterTos, url, drUnitKey);
    }

    /**
     * @return com.deep.deepenterpise.model.vo.gas.DrOrderVo
     * @Auth xyz
     * @Desc //TODO 企业液化气订单信息录入
     * @Time 14:53 2024/6/4
     * @Param [drAddOrderTos, drUnitKey]
     */
    @Override
    public DrOrderVo postDrAddOrder(List<DrAddOrderTo> drAddOrderTos, String drUnitKey) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_ORDER;
        return postApi(drAddOrderTos, url, drUnitKey, DrOrderVo.class);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO 企业液化气客户信息录入/更新/删除
     * @Time 10:58 2024/5/14
     * @Param [drAddMemberTos, drUnitKey]
     */
    @Override
    public DrGasResultVo postDrAddMember(List<DrAddMemberTo> drAddMemberTos) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_MEMBER;
        return postApi(drAddMemberTos, url, null);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO 企业液化气人员培训信息录入/更新/删除
     * @Time 10:58 2024/5/14
     * @Param [drAddStaffTrainingTos]
     */
    @Override
    public DrGasResultVo postDrAddStaffTraining(List<DrAddStaffTrainingTo> drAddStaffTrainingTos) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_STAFF_TRAINING;
        return postApi(drAddStaffTrainingTos, url, null);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO 随瓶安检记录上传
     * @Time 10:59 2024/5/14
     * @Param [drAddCheckBottleTos, drUnitKey]
     */
    @Override
    public DrGasResultVo postDrAddCheckBottle(List<DrAddCheckHistoryTo> drAddCheckBottleTos, String drUnitKey) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_CHECK_BOTTLE;
        return postApi(drAddCheckBottleTos, url, drUnitKey);
    }

    /**
     * @return com.deep.deepenterpise.model.vo.gas.DrGasResultVo
     * @Auth xyz
     * @Desc //TODO 企业液化气瓶入户检查上传
     * @Time 09:47 2024/6/14
     * @Param [drAddCheckBottleTos, drUnitKey]
     */
    @Override
    public DrGasResultVo postDrAddCheckHouse(List<DrAddCheckHistoryTo> drAddCheckBottleTos, String drUnitKey) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_CHECK_HOUSE;
        return postApi(drAddCheckBottleTos, url, drUnitKey);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO 获取检查项
     * @Time 11:39 2024/5/15
     * @Param [type, drUnitKey]
     */
    @Override
    public DrGasCheckItemVo getDrCheckItem() {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.GET_DR_CHECK_ITEM;
        String result = DrOkHttpUtil.httpGet(url);
        return handleResult(result, DrGasCheckItemVo.class);
    }

    /**
     * @return com.deep.deepenterpise.model.vo.gas.DrGasCheckItemVo
     * @Auth xyz
     * @Desc //TODO 获取瓶身检查项
     * @Time 09:30 2024/5/17
     */
    @Override
    public DrGasCheckItemVo getDrCheckBottleItem() {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.GET_DR_CHECK_BOTTLE_ITEM;
        String result = DrOkHttpUtil.httpGet(url);
        DrGasCheckItemVo drGasCheckItemVo = handleResult(result, DrGasCheckItemVo.class);
        if (drGasCheckItemVo == null) {
            return null;
        }
        if (isSuccess(drGasCheckItemVo)) {
            log.error("[获取随瓶安检检查项失败，msg：{}]-------", drGasCheckItemVo.getDrMsg());
            return null;
        }
        return drGasCheckItemVo;
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO 钢瓶日志上传
     * @Time 11:35 2024/5/20
     * @Param [drAddBottleLogTos, drUnitKey]
     */
    @Override
    public DrBottleLogVo postDrAddBottleLog(List<DrAddBottleLogTo> drAddBottleLogTos, String drUnitKey) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_FILLING_BOTTLE_OUT;
        return postApi(drAddBottleLogTos, url, drUnitKey, DrBottleLogVo.class);
    }

    /**
     * @return com.deep.deepenterpise.model.vo.gas.DrGasResultVo
     * @Auth xyz
     * @Desc //TODO 钢瓶流转日志上传
     * @Time 16:10 2024/6/14
     * @Param [drAddCheckBottleTos, drUnitKey]
     */
    @Override
    public DrGasResultVo postDrAddBottleLoopLog(List<DrAddBottleLoopLogTo> drAddBottleLoopLogTos, String drUnitKey) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_BOTTLE_LOOP_LOG;
        return postApi(drAddBottleLoopLogTos, url, drUnitKey, DrBottleLogVo.class);
    }

    /**
     * @Auth xyz
     * @Desc //TODO 企业液化气检查项录入
     * @Time 15:12 2024/6/17
     * @Param [drCheckItems]
     */
    @Override
    public DrGasResultVo postDrAddCheckItem(List<DrCheckItem> drCheckItems, String drUnitKey) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_CHECK_ITEM;
        return postApi(drCheckItems, url, drUnitKey);
    }

    /**
     * @return com.deep.deepenterpise.model.vo.gas.DrGasResultVo
     * @Auth xyz
     * @Desc //TODO 隐患信息录入
     * @Time 13:13 2024/6/26
     * @Param [drSynDangerHistoryVos, drUnitKey]
     */
    @Override
    public DrGasResultVo postDrAddDanger(List<DrSynDangerHistoryVo> drSynDangerHistoryVos, String drUnitKey) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_DANGER;
        return postApi(drSynDangerHistoryVos, url, drUnitKey);
    }

    /**
     * @return com.deep.deepenterpise.model.vo.gas.DrGasResultVo
     * @Auth xyz
     * @Desc //TODO 同步评价记录
     * @Time 10:39 2024/6/29
     * @Param [drAddEvaVos, drUnitKey]
     */
    @Override
    public DrGasResultVo postAddEva(List<DrAddEvaVo> drAddEvaVos, String drUnitKey) {
        String url = drApiResources.getPath() + DrGovernmentApiUrl.POST_DR_ADD_EVA;
        return postApi(drAddEvaVos, url, drUnitKey);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO post请求
     * @Time 17:39 2024/5/20
     * @Param [body, url, drUnitKey]
     */
    public <T> DrGasResultVo postApi(T body, String url, String drUnitKey) {
        return postApi(body, url, drUnitKey, DrGasResultVo.class);
    }

    /**
     * @return com.deep.deepenterpise.common.result.DrResult
     * @Auth xyz
     * @Desc //TODO post请求
     * @Time 09:52 2024/5/14
     * @Param [data, url, token]
     */
    public <B, T extends DrGasResultVo> T postApi(B body, String url, String drUnitKey, Class<T> clazz) {
        Map<String, String> header = new HashMap<>();
        if (StringUtils.isNotBlank(drUnitKey)) {
            String token = drGasAuthHandler.getKey(GasKey.LOGIN_TOKEN_KEY.withSuffix(drUnitKey));
            if (StringUtils.isBlank(token)) {
                return null;
            }
            header.put("drToken", token);
            header.put("drAdmin", "true");
        }
        String result = DrOkHttpUtil.httpPost(url, header, DrGson.toJSONString(body));
        return handleResult(result, clazz);
    }

    /**
     * @return T
     * @Auth xyz
     * @Desc //TODO 处理请求结果
     * @Time 03:46 2024/5/14
     * @Param [result, clazz]
     */
    public static <T extends DrGasResultVo> T handleResult(String result, Class<T> clazz) {
        if (StringUtils.isBlank(result)) {
            log.error("[GAS-API]-------[请求结果为空]-------");
            return null;
        }
        try {
            return DrGson.parseObject(result, clazz);
        } catch (Exception e) {
            log.error("[GAS-API]-------[HandleResult调用失败]-------" + DrCommonUtil.drGetStackTraceInfo(e));
            return null;
        }
    }

    /**
     * @return boolean
     * @Auth xyz
     * @Desc //TODO 判断是否成功
     * @Time 03:46 2024/5/14
     * @Param [drGpsBaseVo]
     */
    public static boolean isSuccess(DrGasResultVo drGasBaseVo) {
        return 200 != drGasBaseVo.getDrCode();
    }

    /**
     * @return java.lang.String
     * @Auth xyz
     * @Desc //TODO 获取token
     * @Time 11:11 2024/5/15
     * @Param [method]
     */
    @Override
    public String getToken(String method, String drUnitKey, String drSecret) {
        // 获取token
        String gasToken = drGasAuthHandler.getKey(GasKey.LOGIN_TOKEN_KEY.withSuffix(drUnitKey));
        // 如果token为空，则重新获取
        if (StringUtils.isBlank(gasToken)) {
            gasToken = getGasToken(method, drUnitKey, drSecret);
        }
        return gasToken;
    }

    /**
     * @return java.lang.String
     * @Auth xyz
     * @Desc //TODO getGasToken
     * @Time 08:20 2024/5/14
     * @Param [userId]
     */
    private synchronized String getGasToken(String method, String drUnitKey, String drSecret) {
        // 再从缓存中获取一遍
        String gasToken = drGasAuthHandler.getKey(GasKey.LOGIN_TOKEN_KEY.withSuffix(drUnitKey));
        if (StringUtils.isNotBlank(gasToken)) {
            return gasToken;
        }
        // 过期重新获取
        String newToken = doGasLogin(method, drUnitKey, drSecret);
        if (StringUtils.isBlank(newToken)) {
            return null;
        }
        drGasAuthHandler.addKeyWithDelay(GasKey.LOGIN_TOKEN_KEY.withSuffix(drUnitKey), newToken);
        return newToken;
    }

    /**
     * @return java.lang.String
     * @Auth xyz
     * @Desc //TODO GPS登录接口，用于获取token等必要数据
     * @Time 08:19 2024/5/14
     * @Param [userId]
     */
    private synchronized String doGasLogin(String method, String drUnitKey, String drSecret) {
        String result = postDrGasToken(drUnitKey, drSecret);
        DrGasTokenVo drGpsLoginVo = DrGovernmentApi.handleResult(result, DrGasTokenVo.class);
        if (drGpsLoginVo == null) {
            log.error("[政府端API，method：{}，获取token失败]-------", method);
            return null;
        }
        if (DrGovernmentApi.isSuccess(drGpsLoginVo)) {
            log.error("[政府端API，method：{}，获取token失败，msg：{}]-------", method, drGpsLoginVo.getDrMsg());
            return null;
        }
        return drGpsLoginVo.getDrData().getDrToken();
    }

}
